﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Web.Mvc;
using NetSurveillance.WebApp.DataServices.Models;
using NetSurveillance.WebApp.Models;
using NetSurveillance.WebApp.Utilities;
using NetSurveillance.WebApp.Exts;
using Resources;
namespace NetSurveillance.WebApp.Controllers
{
    public class SearchController : BaseController
    {
        public ActionResult Search(long? searchId = null, string searchFrom = "current")
        {
            var multiSearchModel = new MultiSearchModel();
            var searchModel = searchId.HasValue
                                  ? DataProvider.SearchService.GetModelById(searchId.Value)
                                  : null;
            if (searchId.HasValue && searchModel != null)
            {
                multiSearchModel.MergeFrom(searchModel);
                //因为searchModel的id类型和multiSearchModel的id类型不一致，所以需要手动设置
                multiSearchModel.Id = searchModel.Id;
            }
            multiSearchModel.SearchFrom = searchFrom;
            LoadSearchViewData(searchFrom);
            return View(multiSearchModel);
        }

        private void LoadSearchViewData(string searchFrom)
        {
            string treeNodeStr;
            if (searchFrom == "current")
            {
                var hosts = DataProvider.HostService.GetAllModels(false, p => p.TaskId == CurrentTask.Id);
                treeNodeStr = SerializeObject(ZTreeUtility.GenerateHostNodes(hosts, null));
            }
            else
            {
                var cases = DataProvider.CaseService.GetAllModels();
                treeNodeStr = SerializeObject(GenerateCaseNodes(cases));
            }
            ViewBag.TreeNode = treeNodeStr;
            var protocols = SupportUtility.GetSupportProtocols();
            ViewBag.Protocols = new SelectList(protocols, "Name", "DisplayText");
        }

        private IList<ZTreeNode> GenerateCaseNodes(IEnumerable<Case> cases)
        {
            IList<ZTreeNode> caseNodes = new List<ZTreeNode>();
            foreach (var @case in cases)
            {
                long caseId = @case.Id;
                var caseNode = new ZTreeNode {Name = @case.Name, Children = new List<ZTreeNode>()};
                var tasks = DataProvider.TaskService.GetAllModels(false, p => p.CaseId == caseId);
                foreach (var task in tasks)
                {
                    long taskId = task.Id;
                    var hosts = DataProvider.HostService.GetAllModels(false, p => p.TaskId == taskId);
                    var taskNode = new ZTreeNode
                        {
                            Name = task.Name,
                            Children = ZTreeUtility.GenerateHostNodes(hosts, null)
                        };
                    caseNode.Children.Add(taskNode);
                }
                caseNodes.Add(caseNode);
            }
            return caseNodes;
        }

        [HttpPost]
        public ActionResult Search(MultiSearchModel multiSearchModel)
        {
            if (ModelState.IsValid)
            {
                var multisearch = multiSearchModel.Id.HasValue
                                      ? DataProvider.SearchService.GetModelById(multiSearchModel.Id.Value)
                                      : new MultiSearch();
                if (multiSearchModel.Id.HasValue)
                    multisearch.LastModifiedTime = DateTime.Now;
                else
                    multisearch.CreatedUserId = CurrentUser.Id;
                multisearch.TaskId = CurrentTask.Id;
                multisearch.MergeFrom(multiSearchModel);
                var serviceResult = DataProvider.SearchService.Save(multisearch);
                ModelState.AddModelError("",
                                         serviceResult.ExecutedSuccess
                                             ? MessageResource.Save_Success
                                             : MessageResource.Save_Error);
            }
            LoadSearchViewData(multiSearchModel.SearchFrom);
            return View(multiSearchModel);
        }

        [HttpPost]
        public ActionResult DeleteSearch(string searchIds)
        {
            if (!string.IsNullOrWhiteSpace(searchIds))
            {
                string[] ids = searchIds.Split(new[] { ',' });
                bool isSuccess = true;
                for (int i = 0; i < ids.Length; i++)
                {
                    var searchId = long.Parse(ids[i]);
                    if (!isSuccess)
                    {
                        return Json(new AjaxResult(false, ids[i - 1] + "删除操作失败!"));
                    }
                    var currentSearchModel = DataProvider.SearchService.GetModelById(searchId);
                    currentSearchModel.StatusToken = 0;
                    var serverResult =
                        DataProvider.SearchService.UpdateOnly(currentSearchModel, p => p.StatusToken,
                                                              p => p.Id == searchId);
                    isSuccess = serverResult.ExecutedSuccess;
                }
                return Json(new AjaxResult(true));
            }
            return Json(new AjaxResult(false, "参数丢失！"));
        }


        public ActionResult IMSearch(long? imSearchId = null, string searchFrom = "current")
        {
            var imDataSearch = imSearchId.HasValue
                                  ? DataProvider.IMDataSearchService.GetModelById(imSearchId.Value)
                                  : null;
            var imSearchModel = new IMDataSearchModel();
            
            if (imSearchId.HasValue && imDataSearch != null)
            {
                imSearchModel.MergeFrom(imDataSearch);
                imSearchModel.Id = imSearchId.Value;
            }
            LoadIMSearchViewData(searchFrom, imDataSearch == null ? null : imDataSearch.Protocol);
            return View(imSearchModel);
        }

        private void LoadIMSearchViewData(string searchFrom, string protocol)
        {
            string treeNodeStr;
            if (searchFrom == "current")
            {
                var hosts = DataProvider.HostService.GetAllModels(false, p => p.TaskId == CurrentTask.Id);
                treeNodeStr = SerializeObject(ZTreeUtility.GenerateHostNodes(hosts, null));
            }
            else
            {
                var cases = DataProvider.CaseService.GetAllModels();
                treeNodeStr = SerializeObject(GenerateCaseNodes(cases));
            }
            ViewBag.TreeNode = treeNodeStr;
            var protocols = SupportUtility.GetSupportProtocols().Where(p => p.IsIM);
            ViewBag.Protocols = new SelectList(protocols, "Name", "DisplayText");
            var localAccounts = Enumerable.Empty<DataIMRecord>();
            var remoteAccts = Enumerable.Empty<DataIMRecord>();
            if (!string.IsNullOrEmpty(protocol))
            {
                localAccounts = DataProvider.DataIMRecordService.GetLocalIMs(CurrentTask.Id, protocol);
                remoteAccts = DataProvider.DataIMRecordService.GetRemoteIMs(CurrentTask.Id, protocol);
            }
            ViewBag.LocalAccts = new SelectList(localAccounts, "LocalNumber", "LocalName");
            ViewBag.RemoteAccts = new SelectList(remoteAccts, "RemoteNumber", "RemoteName");
        }

        [HttpPost]
        public ActionResult IMSearch(IMDataSearchModel imDataSearchmModel)
        {
            if (ModelState.IsValid)
            {
                var imDataSearch = imDataSearchmModel.Id.HasValue
                                      ? DataProvider.IMDataSearchService.GetModelById(imDataSearchmModel.Id.Value)
                                      : new IMDataSearch();
                if (imDataSearchmModel.Id.HasValue)
                    imDataSearch.LastModifiedTime = DateTime.Now;
                else
                    imDataSearch.CreatedUserId = CurrentUser.Id;
                imDataSearch.TaskId = CurrentTask.Id;
                imDataSearch.MergeFrom(imDataSearchmModel);
                var serviceResult = DataProvider.IMDataSearchService.Save(imDataSearch);
                ModelState.AddModelError("",
                                         serviceResult.ExecutedSuccess
                                             ? MessageResource.Save_Success
                                             : MessageResource.Save_Error);
            }
            LoadIMSearchViewData(imDataSearchmModel.SearchFrom, imDataSearchmModel.Protocol);
            return View(imDataSearchmModel);
        }

        [ChildActionOnly]
        public ActionResult CheckQueryLists(string type)
        {
            List<long> searchIds = null;
            if (!string.IsNullOrWhiteSpace(type))
            {
                if (type == "search")
                {
                    searchIds = 
                        DataProvider.SearchService.GetAllModels().OrderBy(p => p.Id).Select(p => p.Id).AsList();
                }
                if (type == "imSearch")
                {
                    searchIds = 
                        DataProvider.IMDataSearchService.GetAllModels().OrderBy(p => p.Id).Select(p => p.Id).AsList();
                }
            }
            else
            {
                ViewData["Error"] = "error";
            }
            return View(searchIds);
        }

        public ActionResult SearchResult(MultiSearch multiSearch, string searchFrom,
                                         long[] hostIds, DataRecordListModel drlModel)
        {
            int totalCount;
            int pageSize = PageSize;
            if (drlModel == null)
                drlModel = new DataRecordListModel {OrderField = "Id"};
            int pageIndex = drlModel.PageIndex <= 0
                                ? (drlModel.PageIndex = 1)
                                : drlModel.PageIndex;
            var drFilter =
                DataContainer.Read<DataRecordFilter>(PresetValues.SessionKeys.SearchFilter) ??
                new DataRecordFilter();
            drFilter.Order = drlModel.Order;
            drFilter.OrderField = drlModel.OrderField;
            drFilter.IsTakeAll = drlModel.DisplayAll;
            drFilter.IsTakeNoTitle = IsShowNoTitleRecord;
            var dataRecords =
                DataProvider.DataRecordService.GetDataRecords(hostIds, multiSearch,
                                                              pageIndex, pageSize, out totalCount,
                                                              drFilter);
            drlModel.DataRecords = dataRecords;
            ViewBag.SupportFields = SupportUtility.GetDisplayField();
            ViewBag.DisplayFields =
                DataProvider.DisplayFieldService.GetAllModels().Select(p => p.FieldName).ToList();
            ViewBag.MultiSearchId = multiSearch.Id;
            int currCount = pageIndex <= 1 ? pageSize : pageIndex*pageSize;
            string currCountDesc = string.Format("{0}-{1}",
                                                 (pageIndex <= 1 ? 1 : (pageIndex - 1)*pageSize),
                                                 (totalCount > currCount) ? currCount : totalCount);
            drlModel.TotalCount = totalCount;
            drlModel.CurrentCount = currCountDesc;
            drlModel.IsLastPage = currCount >= totalCount;
            drlModel.TaskStatus = CurrentTask == null
                                                 ? TaskStatusType.Stop
                                                 : CurrentTask.TaskStatus;
            ModelState.Clear();
            string viewName = searchFrom == "current"
                                  ? "~/Views/Task/DataRecordList.cshtml"
                                  : "~/Views/Task/HistoryDataRecordList.cshtml";
            return View(viewName, drlModel);
        }

        public ActionResult IMSearchResult(IMDataSearch imDataSearch,
                                           DataIMRecordListModel dataIMRLModel, long[] hostIds)
        {
            if (dataIMRLModel == null)
                dataIMRLModel = new DataIMRecordListModel {OrderField = "Id"};
            if (!dataIMRLModel.TaskId.HasValue || dataIMRLModel.TaskId.Value <= 0)
                dataIMRLModel.TaskId = CurrentTask != null ? CurrentTask.Id : -1;
            var dimrFilter = new DataIMRecordFilter { IsTakeAll = dataIMRLModel.DisplayAll };
            dimrFilter.MergeFrom(dataIMRLModel);
            int pageSize = PageSize,
                pageIndex = dataIMRLModel.PageIndex;
            int? totalCount;
            var dataIMRecords =
                DataProvider.DataIMRecordService.GetDataIMRecords(imDataSearch, dimrFilter, hostIds,
                                                                  pageIndex, pageSize,
                                                                  out totalCount);
            dataIMRLModel.DataIMRecords = dataIMRecords;
            if (CurrentTask != null)
                dataIMRLModel.TaskStatus = CurrentTask.TaskStatus;
            int currCount = pageIndex <= 1 ? pageSize : pageIndex * pageSize;
            string currCountDesc = string.Format("{0}-{1}", (pageIndex <= 1 ? 1 : (pageIndex - 1) * pageSize),
                                                 (totalCount > currCount) ? currCount : totalCount);
            if (dataIMRLModel.DisplayAll)
                currCountDesc = string.Format("1-{0}", totalCount);
            dataIMRLModel.TotalCount = totalCount.HasValue ? totalCount.Value : 0;
            dataIMRLModel.CurrentCount = currCountDesc;
            dataIMRLModel.IsLastPage = currCount >= totalCount;
            ViewBag.SearchId = imDataSearch == null ? -1 : imDataSearch.Id;
            return View("~/Views/Task/DataIMRecordList.cshtml", dataIMRLModel);
        }
    }
}
